package channel

import (
	reqContext "context"
	"fmt"
	"strings"
	"time"

	"github.com/hyperledger/fabric-protos-go/common"
	"github.com/hyperledger/fabric-sdk-go/pkg/client/resmgmt"
	"github.com/hyperledger/fabric-sdk-go/pkg/common/errors/retry"
	"github.com/hyperledger/fabric-sdk-go/pkg/common/providers/core"
	"github.com/hyperledger/fabric-sdk-go/pkg/common/providers/fab"
	"github.com/hyperledger/fabric-sdk-go/pkg/core/config/lookup"
	"github.com/hyperledger/fabric-sdk-go/pkg/fabsdk"
	"github.com/pkg/errors"
)

//requestOptions contains options for operations performed by ResourceMgmtClient
type RequestOptions struct {
	//Targets      []fab.Peer                        // target peers
	//TargetFilter fab.TargetFilter                  // target filter
	//Orderer      fab.Orderer                       // use specific orderer
	//Timeouts     map[fab.TimeoutType]time.Duration //timeout options for resmgmt operations
	//ParentContext reqContext.Context                //parent grpc context for resmgmt operations
	//Retry         retry.Opts
	// signatures for channel configurations, if set, this option will take precedence over signatures of SaveChannelRequest.SigningIdentities
	//Signatures []*common.ConfigSignature
}

// WithTargets allows overriding of the target peers for the request.
//func WithTargets(targets ...fab.Peer) RequestOption {
//return func(ctx context.Client, opts *RequestOptions) error {

//// Validate targets
//for _, t := range targets {
//if t == nil {
//return errors.New("target is nil")
//}
//}

//opts.Targets = targets
//return nil
//}
//}

//requestOptions contains options for operations performed by ResourceMgmtClient
type requestOptions struct {
	Targets       []fab.Peer                        // target peers
	TargetFilter  fab.TargetFilter                  // target filter
	Orderer       fab.Orderer                       // use specific orderer
	Timeouts      map[fab.TimeoutType]time.Duration //timeout options for resmgmt operations
	ParentContext reqContext.Context                //parent grpc context for resmgmt operations
	Retry         retry.Opts
	// signatures for channel configurations, if set, this option will take precedence over signatures of SaveChannelRequest.SigningIdentities
	Signatures []*common.ConfigSignature
}

//func WithTarget(target fab.Peer) resmgmt.RequestOption {
//return func(ctx context.Client, opts *requestOptions) error {

//return nil
//}
//}

func orgTargetPeers(orgs []string, configBackend ...core.ConfigBackend) ([]string, error) {
	fmt.Println("---------> orgTargetPeers ----------- 1")
	networkConfig := fab.NetworkConfig{}
	err := lookup.New(configBackend...).UnmarshalKey("organizations", &networkConfig.Organizations)
	if err != nil {
		fmt.Println("---------> orgTargetPeers ----------- 2")
		return nil, errors.WithMessage(err, "failed to get organizations from config ")
	}
	fmt.Println("---------> orgTargetPeers ----------- 3")

	var peers []string
	for _, org := range orgs {
		fmt.Println(org)
		orgConfig, ok := networkConfig.Organizations[strings.ToLower(org)]
		if !ok {
			continue
		}
		peers = append(peers, orgConfig.Peers...)
	}
	return peers, nil
}
func GetChannels(sdk *fabsdk.FabricSDK, orgAdmin, orgName, peerUrl string) []string {
	var chlist []string
	chlist = make([]string, 0)
	clientContext := sdk.Context(fabsdk.WithUser(orgAdmin), fabsdk.WithOrg(orgName))
	//fmt.Println(clientContext)

	resMgmtClient, err := resmgmt.New(clientContext)
	if err != nil {
		panic(err)
	}
	//fmt.Println(resMgmtClient)
	target := peerUrl
	response, err := resMgmtClient.QueryChannels(
		resmgmt.WithTargetEndpoints(target),
		resmgmt.WithRetry(retry.DefaultResMgmtOpts),
	)
	if err != nil {
		panic(err)
	}

	for _, chl := range response.Channels {
		//fmt.Printf("  |---> [%d] %s\n", i, chl.ChannelId)
		chlist = append(chlist, chl.ChannelId)
	}
	return chlist
}
